Skip to content

Allow saving some PA images as PNG - #9833

Open
akx wants to merge 1 commit into
python-pillow:mainfrom
akx:png-pa
Open

Allow saving some PA images as PNG#9833
akx wants to merge 1 commit into
python-pillow:mainfrom
akx:png-pa

Conversation

@akx

@akx akx commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

Limitation found while working on #9829: we weren't able to save PA (palette index + alpha band) images into PNG at all. This adds limited capacity for that: in case each index+alpha combination occurs only once across the image, we can save it as P+RGBA-palette instead.

An example PA file saved with Pillow - those are solid primaries! 😄

temp

Comment thread src/PIL/PngImagePlugin.py
if index_alpha.setdefault(index, alpha_value) != alpha_value:
msg = (
"cannot write mode PA as PNG: "
"a palette entry is used with multiple alpha values"

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not saying we need to go down this rabbit hole, but if there are less than 256 entries, it would be possible to achieve two alpha values for one palette entry by copying the entry and remapping it within the image. So a (255, 0, 0) entry with 100 alpha and 200 alpha could become two (255, 0, 0) entries with individual alphas.

@akx akx Jul 29, 2026

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That could be a future enhancement, but it'd also mean we'd write a different palette than the user originally passed in into the PNG. (The roundtrip test here would probably fail.)

@radarhere

Copy link
Copy Markdown
Member

This would be the only conversion done when saving a single frame PNG. I wonder if it isn't better/consistent to require users to convert the image before the save?

You're converting a PA image, to P with RGBA palette. Maybe a generic convert() from PA to P should generate an RGBA palette using the logic you've written here?

@akx

akx commented Jul 29, 2026

Copy link
Copy Markdown
Contributor Author

Maybe a generic convert() from PA to P should generate an RGBA palette using the logic you've written here?

I thought about that too (or rather whether this function should belong somewhere else), and I'm not sure.

convert()ing PA to P currently makes every pixel opaque. This probably hasn't been documented properly, so maybe having PA-to-P conversion in the general case do this (when possible) would be an improvement?

Anyway, while looking at this (comment!) I also found #9834...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants